<template>
  <div class="elec-bg">
    <el-card class="elec-card" :body-style="{ padding: '20px' }">
      <template #header>
        <span class="card-title">电价信息管理</span>
      </template>
      <el-form :model="queryParams" ref="queryFormRef" size="small" :inline="true" v-show="showSearch"
        label-width="100px">
        <el-form-item label="电价名称" prop="price_name">
          <el-input v-model="queryParams.price_name" placeholder="请输入电价名称" clearable
            @keyup.enter.native="handleQuery" />
        </el-form-item>
      </el-form>

      <el-row :gutter="10" class="action-btn-row">
        <el-col :span="1.5">
          <el-button class="action-btn primary" type="primary" plain size="default" @click="handleAdd">
            <Plus /> 新增
          </el-button>
        </el-col>
        <el-col :span="1.5">
          <el-button class="action-btn danger" type="danger" plain size="default" :disabled="multiple"
            @click="deleteByIds">
            <Delete /> 删除
          </el-button>
        </el-col>
        <el-col :span="1.5">
          <el-button class="action-btn warning" type="warning" plain size="default" :disabled="multiple"
            @click="exportByIds">
            <Download /> 导出
          </el-button>
        </el-col>
        <el-col :span="1.5">
          <el-upload :show-file-list="false" accept=".xlsx,.xls" :before-upload="handleExcelImport">
            <el-button class="action-btn import" type="success" plain size="default">
              <Upload />导入
            </el-button>
          </el-upload>
        </el-col>
        <el-col :span="1.5">
          <el-button class="action-btn success" type="success" plain size="default" :disabled="multiple"
            @click="predictByIds">
            <Refresh /> 预测
          </el-button>
        </el-col>

      </el-row>

      <el-table v-loading="loading" :data="filteredInfoList" @selection-change="handleSelectionChange"
        @expand-change="handleExpandChange" border>
        <!-- 展开行：显示时段电价 -->
        <el-table-column type="expand">
          <template #default="props">
            <div class="expand-container">
              <!-- 加载状态 -->
              <el-loading v-if="expandedLoading[props.row.priceId]" text="加载数据中..." fullscreen="false" />

              <template v-else>
                <!-- 操作按钮（居右显示） -->
                <div class="expand-actions" style="margin-bottom: 10px; text-align: right;">
                  <el-button type="warning" plain size="default" @click="handleExport(props.row)">
                    <Download /> 导出
                  </el-button>
                </div>

                <!-- 左右分栏容器 -->
                <div class="split-layout">
                  <!-- 左侧：ECharts 图表（40%宽度） -->
                  <!-- 左侧：引入图表组件 -->
                  <PriceChart class="chart-container" :data="props.row.values || []"
                    :title="0" />

                  <!-- 右侧：子表格（60%宽度） -->
                  <div class="table-container">
                    <el-table :data="props.row.values || []" border height="300px" size="small" style="width: 100%;">
                      <el-table-column label="序号" type="index" width="60" align="center" />
                      <el-table-column label="时间点" prop="time_point" align="center">
                        <template #default="scope">
                          {{ formatTime(scope.row.time_point) }}
                        </template>
                      </el-table-column>
                      <el-table-column label="电价金额（元）" prop="price_amount" align="center" />
                    </el-table>
                  </div>
                </div>
              </template>
            </div>
          </template>
        </el-table-column>
        <el-table-column type="selection" width="55" align="center" />
        <el-table-column label="ID" width="100" align="center" prop="price_id" />
        <el-table-column label="划分周期单位" align="center" prop="period_unit" />
        <el-table-column label="划分周期" align="center" prop="period" />
        <el-table-column label="电价类型" align="center">
          <template #default="scope">
            {{ getPriceTypeName(scope.row.price_type) }}
          </template>
        </el-table-column>
        <el-table-column label="电价名称" width="300" align="center" prop="price_name" />
        <el-table-column label="划分粒度" align="center" prop="granularity" />
        <el-table-column label="操作" align="center" class-name="small-padding fixed-width">
          <template #default="scope">
            <el-button size="small" type="danger" @click="handleDelete(scope.row)" class="icon-btn">
              <Delete /> 删除
            </el-button>
          </template>
        </el-table-column>
      </el-table>

      <!--    <pagination-->
      <!--        v-show="total > 0"-->
      <!--        :total="total"-->
      <!--        :page.sync="queryParams.pageNum"-->
      <!--        :limit.sync="queryParams.pageSize"-->
      <!--        @pagination="getList"-->
      <!--    />-->

      <!-- 添加或修改对话框 -->
      <el-dialog :title="title" v-model="open" width="700px" max-height="600px" append-to-body>
        <el-form ref="formRef" :model="form" :rules="rules" label-width="110px" class = "elect-form">
          <!-- 划分周期单位：下拉框选择 day/week/hour -->
          <el-form-item label="划分周期单位" prop="period_unit">
            <el-select v-model="form.period_unit" placeholder="请选择划分周期单位"
                       @change="handleperiod_unitChange" class="form-select" disabled>
              <!-- 选择变化时触发粒度联动 -->
<!--              <el-option label="小时" value="hour" />-->
              <el-option label="天" value="day" />
<!--              <el-option label="周" value="week" />-->
            </el-select>
          </el-form-item>

          <!-- 划分周期：手动输入 -->
          <el-form-item label="划分周期" prop="period">
            <el-input v-model="form.period"
                      placeholder="请输入划分周期（如：1表示1个单位周期）"
                      class="form-input"
                      disabled/>
          </el-form-item>

          <!-- 划分粒度：根据周期单位动态变化选项 -->
          <el-form-item label="划分粒度" prop="granularity">
            <el-select v-model="form.granularity" placeholder="请选择划分粒度"
                       @change="handleGranularityChange" class="form-select"
                       disabled>
              <!-- 动态渲染粒度选项 -->
              <el-option v-for="item in granularityOptions" :key="item.value" :label="item.label" :value="item.value" />
            </el-select>
          </el-form-item>

          <el-form-item label="电价类型" prop="price_type">
            <el-select v-model="form.price_type" placeholder="请选择电价类型" @change="handleprice_typeChange" class="form-select">
              <el-option label="光电" value="0" />
              <el-option label="风电" value="1" />
              <el-option label="国网" value="2" />
            </el-select>
          </el-form-item>

          <!-- 电价名称-->
          <el-form-item label="电价名称" prop="price_name">
            <el-input v-model="form.price_name" placeholder="请输入电价名称" class="form-input"> </el-input>
          </el-form-item>

          <!-- 新增：电价时间点表格（根据粒度动态生成） -->
          <el-form-item label="时段电价" prop="values" class="values-table">
            <div class="table-container_dialog">
              <div class="add-button-container" >
                <el-button type="info" :icon="Plus" circle class="add-btn" @click="addRow"/>
              </div>
              <el-table :data="form.values" height="300px" border style="width: 100%">
                <el-table-column label="序号" type="index" width="60" align="center" />
                <el-table-column label="时间点" prop="time_point" width="200px" align="center">
                  <template #default="scope">
                    <el-date-picker v-model="scope.row.time_point" type="datetime" format="YYYY-MM-DD HH:mm:ss"
                      value-format="YYYY-MM-DD HH:mm:ss" placeholder="选择时间点" size="default" style="width: 100%;"
                      @change="handleTimeChange(scope.$index)" />
                  </template>
                </el-table-column>
                <el-table-column label="电价金额（元）" align="center">
                  <template #default="scope">
                    <el-input v-model.number="scope.row.price_amount" placeholder="请输入电价" type="number" min="0"
                      step="0.01" @change="handlePriceChange(scope.$index)" />
                  </template>
                </el-table-column>
                <el-table-column label="操作" width="100" align="center">
                  <template #default="scope">
                    <el-button type="danger" size="small" @click="removeRow(scope.$index)">
                      删除
                    </el-button>
                  </template>
                </el-table-column>
              </el-table>
            </div>
          </el-form-item>
        </el-form>
        <div slot="footer" class="dialog-footer">
          <el-button @click="cancel" class="cancel-btn">取 消</el-button>
          <el-button type="primary" @click="submitForm" class="confirm-btn">确 定</el-button>
        </div>
      </el-dialog>
    </el-card>
  </div>
</template>

<script setup>
import { ref, reactive, onMounted, nextTick, computed, watch } from 'vue';
import { useRouter } from 'vue-router';
import { ElMessage, ElMessageBox } from 'element-plus';
import * as echarts from 'echarts';
import * as XLSX from "xlsx";
// 导入 API 服务
import { listInfo, getInfo, delInfo, addInfo, updateInfo, exportInfoByIds, deleteInfoByIds, predictElectricPrice } from "../api/system/elecPrice.js";

// 导入图标组件
import {Edit, Delete, Plus, Search, Refresh, Download, Upload} from '@element-plus/icons-vue';
import PriceChart from "../components/PriceChart.vue";

import { downloadFile } from "../utils/download.js";
// 表单引用
const queryFormRef = ref(null);
const formRef = ref(null);
const globalTimeList = ref([])
// 状态管理
const loading = ref(true);
const ids = ref([]);
const single = ref(true);
const multiple = ref(true);
const showSearch = ref(true);
const total = ref(0);
const infoList = ref([]);
const title = ref('');
const open = ref(false);
// 粒度选项（根据周期单位动态生成）
const granularityOptions = ref([]);
// 查询参数
const queryParams = reactive({
  pageNum: 1,
  pageSize: 10,
  period_unit: null,
  period: null,
  price_type: null,
  granularity: null,
  price_name: null
});
const handleExcelImport = (file) => {
  const reader = new FileReader()
  let requestBody = {}
  reader.onload = (e) => {
    const data = e.target.result
    const workbook = XLSX.read(data, { type: 'binary' })
    const firstSheetName = workbook.SheetNames[0]
    const worksheet = workbook.Sheets[firstSheetName]
    const jsonData = XLSX.utils.sheet_to_json(worksheet)
    // jsonData 就是Excel里的数据数组
    let values = []
    jsonData.forEach(item => {
      values.push({
        'time_point': item['时间'],
        'price_amount': item['价格值'],
      })
    })
    requestBody = {
      'period_unit': 'day',
      'period': 1,
      'granularity': 24,
      'icon': '',
      'background': '',
      'price_name': jsonData[0]['价格名称'],
      'price_type': jsonData[0]['电价类别ID'],
      'values': values
    }
    if(requestBody.price_name == null ||requestBody.values == null ||requestBody.price_type == null){
      ElMessage.error('请检查文件格式')
      return
    }
    console.log(requestBody)
    addInfo(requestBody).then(res => {
      ElMessage.success('导入成功')
      getList()
    }).catch(error => {
      ElMessage.error('导入失败')
    })
  }
  reader.readAsBinaryString(file)
}
// 表单数据
const form = reactive({
  priceId: null,
  period_unit: 'day',
  period: 1,
  price_type: null,
  granularity: 24,
  price_name: null,
  values: []    // 时段电价数组：[{time_point, price_amount}, ...]
});

// 表单校验规则
const rules = reactive({
  period_unit: [
    { required: true, message: "划分周期单位不能为空", trigger: "blur" }
  ],
  period: [
    { required: true, message: "划分周期不能为空", trigger: "blur" }
  ],
  price_type: [
    { required: true, message: "电价类型不能为空", trigger: "change" }
  ],
  granularity: [
    { required: true, message: "划分粒度不能为空", trigger: "blur" }
  ],
  price_name: [
    { required: true, message: "电价名称不能为空", trigger: "blur" }
  ]
});
// 在<script setup>中添加或修正此方法
const formatTime = (isoTime) => {
  if (!isoTime) return ''; // 处理空值
  const date = new Date(isoTime);
  // 格式化时间为 "YYYY-MM-DD HH:mm:ss"
  return date.toLocaleString('zh-CN', {
    year: 'numeric',
    month: '2-digit',
    day: '2-digit',
    hour: '2-digit',
    minute: '2-digit',
    second: '2-digit',
    hour12: false
  }).replace(/\//g, '-'); // 将斜杠替换为横杠（如 2025/07/11 → 2025-07-11）
};
// 存储展开行的加载状态（避免重复请求）
const expandedLoading = ref({});
// 展开/折叠行时触发
// 展开/折叠行时触发（核心修改）
const handleExpandChange = async (row, expandedRows) => {
  if (expandedRows.includes(row) && (!row.values || row.values.length === 0)) {
    const priceId = row.price_id;
    console.log("加载时段数据中", row);
    expandedLoading.value[priceId] = true;

    getInfo(priceId).then(response => {
      console.log("加载时段数据成功", response.data)
      const { time_list, value_list } = response.data.data; // 从接口获取两个数组

      // 关键：合并 time_list 和 value_list 为子表格数据
      row.values = time_list.map((time, index) => ({
        time_point: time, // 时间点对应 time_list 的元素
        price_amount: value_list[index] || 0 // 电价对应 value_list 的元素（默认0）
      }));
      globalTimeList.value = row.values
      console.log(row.values, 1, globalTimeList.value);
      // 触发视图更新
      infoList.value = [...infoList.value];
    }).catch(error => {
      ElMessage.error('加载时段数据失败');
      console.error(error);
    }).finally(() => {
      expandedLoading.value[priceId] = false;
    });
  }
};
// 粒度选择变化时，生成时间点
const handleGranularityChange = () => {
  generateTimePoints();
};
// 周期单位变化时，更新粒度选项
const handleperiod_unitChange = (value) => {
  // 清空当前粒度选择（避免选项不匹配）
  form.granularity = null;
  form.values = [];

  // 根据周期单位生成对应粒度选项
  switch (value) {
    case 'day':
      // 天：1-24小时
      granularityOptions.value = Array.from({ length: 24 }, (_, i) => ({
        label: `${i + 1}小时`,
        value: i + 1
      }));
      break;
    case 'week':
      // 周：按天划分（1-7天）或按小时划分（1-168小时，每周7*24=168小时）
      // 这里选择按天划分，更符合周级调度习惯
      granularityOptions.value = Array.from({ length: 7 }, (_, i) => ({
        label: `${i + 1}天`,
        value: i + 1
      }));
      break;
    case 'hour':
      // 小时：按15分钟粒度划分（1-4个区间，每15分钟为1单位）
      granularityOptions.value = [
        { label: '15分钟', value: 1 },
        { label: '30分钟', value: 2 },
        { label: '45分钟', value: 3 },
        { label: '60分钟', value: 4 }
      ];
      break;
    default:
      granularityOptions.value = [];
  }
  // 新增：如果已有粒度值，立即生成时间点
  // 新增：如果已有粒度值，立即生成时间点
  if (form.granularity) {
    generateTimePoints();
  }
};
//根据id批量导出


// 根据粒度生成时间点（核心逻辑）
const generateTimePoints = () => {
  form.values = []; // 清空现有数据

  const { period_unit, granularity } = form;
  if (!period_unit || !granularity) return;

  // 生成当前日期（可根据需求改为周期起始日期）
  const baseDate = new Date();
  const year = baseDate.getFullYear();
  const month = String(baseDate.getMonth() + 1).padStart(2, '0');
  const day = String(baseDate.getDate()).padStart(2, '0');
  const baseDateStr = `${year}-${month}-${day}`;

  // 1. 周期单位为"天"（day）：生成0-23点
  if (period_unit === 'day' && granularity === 24) {
    for (let i = 0; i < 24; i++) {
      const hour = String(i).padStart(2, '0');
      form.values.push({
        time_point: `${baseDateStr} ${hour}:00:00`, // 格式：2025-07-11 00:00:00
        price_amount: null // 初始为空，等待用户输入
      });
    }
  }

  // 2. 周期单位为"周"（week）：生成周一到周日
  if (period_unit === 'week' && granularity === 7) {
    for (let i = 0; i < 7; i++) {
      const tempDate = new Date(baseDate);
      tempDate.setDate(baseDate.getDate() + i); // 往后推i天
      const weekDay = tempDate.toLocaleDateString('zh-CN', { weekday: 'long' }); // 星期几
      const dateStr = `${tempDate.getFullYear()}-${String(tempDate.getMonth() + 1).padStart(2, '0')}-${String(tempDate.getDate()).padStart(2, '0')}`;
      form.values.push({
        time_point: `${dateStr}（${weekDay}）`, // 格式：2025-07-11（星期五）
        price_amount: null
      });
    }
  }

  // 3. 周期单位为"小时"（hour）：生成4个15分钟
  if (period_unit === 'hour' && granularity === 4) {
    const hour = String(baseDate.getHours()).padStart(2, '0');
    const minutes = ['00', '15', '30', '45'];
    minutes.forEach(min => {
      form.values.push({
        time_point: `${baseDateStr} ${hour}:${min}:00`, // 格式：2025-07-11 14:00:00
        price_amount: null
      });
    });
  }
};


// 处理时间修改
const handleTimeChange = (index) => {
  // 获取当前行数据
  const row = form.values[index];
  if (row.time_point) {
    // 转换为ISO格式
    const date = new Date(row.time_point);
    row.time_point = date.toISOString();
    console.log(`第${index + 1}行时间已更新为:`, row.time_point);
  }
};

// 处理电价值修改
const handlePriceChange = (index) => {
  const row = form.values[index];
  console.log(`第${index + 1}行电价已更新为:`, row.price_amount);
};

// 辅助函数：将 YYYY-MM-DD HH:mm:ss 转换为 ISO 格式
const formatToISODate = (dateStr) => {
  if (!dateStr) return null;

  // 处理带空格的日期时间格式
  const isoDate = dateStr.replace(' ', 'T') + 'Z';
  return new Date(isoDate).toISOString();
};
// 添加新行
const addRow = () => {
  // 获取当前时间作为默认值
  const now = new Date();
  const formattedTime = now.toISOString().slice(0, 19).replace('T', ' ');

  // 添加新行到表格末尾
  form.values.push({
    time_point: formattedTime,
    price_amount: 0
  });
  console.log("时段电价数据", form.values)
};

//处理名称和类型的联动
const handleprice_typeChange = (selectedValue) => {
  // 1. 将value赋值给price_type
  form.price_type = selectedValue;

  // 2. 根据value查找对应的label
  const selectedOption = [
    { label: "光电", value: "0" },
    { label: "风电", value: "1" },
    { label: "国网", value: "2" }
  ].find(item => item.value === selectedValue);

  // 3. 将label赋值给price_name
  // if (selectedOption) {
  //   form.price_name = selectedOption.label;
  // }
};

// 删除行
const removeRow = (index) => {
  form.values.splice(index, 1);
};
// 生命周期钩子
const typePie = ref(null);
const typeBar = ref(null);
const trendLine = ref(null);
const selectedType = ref('全部');
const trendType = ref('');
const showTrend = ref(false);

const getTypeName = (name) => (name || '').replace(/价$/, '') + '价';

const filteredInfoList = computed(() => {
  if (!queryParams.price_name || !queryParams.price_name.trim()) {
    return infoList.value; // 无搜索词时返回全部数据
  }
  const query = queryParams.price_name.trim().toLowerCase();
  return infoList.value.filter(item => item.price_name.toLowerCase().includes(query));
});
// 类型名严格用原始price_name
const typeOptions = computed(() => {
  const set = new Set();
  infoList.value.forEach(item => set.add(item.price_name));
  return Array.from(set);
});


const getPriceTypeName = (type) => {
  const map = {
    0: '光电',
    1: '风电',
    2: '国网'
  };
  return map[type] || type; // 默认返回原值，避免未知类型
};

const avgPriceByType = computed(() => {
  if (!selectedType.value) return 0;
  let total = 0, count = 0;
  infoList.value.forEach(item => {
    if (item.price_name === selectedType.value) {
      (item.values || []).forEach(v => {
        if (v.price_amount != null) {
          total += Number(v.price_amount);
          count++;
        }
      });
    }
  });
  return count ? (total / count).toFixed(2) : 0;
});

// 其余统计卡片、柱状图自动刷新
watch(infoList, () => {
  nextTick(() => {
    renderTypePie();
    renderTypeBar();
  });
}, { deep: true, immediate: true });

// 1. 页面加载时，selectedType默认选中第一个类型，并显示趋势图
onMounted(() => {
  getList().then(() => {
    if (typeOptions.value.length > 0) {
      selectedType.value = typeOptions.value[0];
      trendType.value = typeOptions.value[0];
      showTrend.value = true;
      nextTick(() => renderTrendLine(typeOptions.value[0]));
    }
  });
});
// 2. 切换下拉框时，趋势图自动联动
watch(selectedType, (val) => {
  if (val) {
    trendType.value = val;
    showTrend.value = true;
    nextTick(() => renderTrendLine(val));
  }
});

// 1. 删除顶部柱状图卡片
// 找到el-row.stat-row下的el-col :span="6"，其el-card内有<div ref="typeBar" style="height: 90px;"></div>和“各类型平均电价”
// 直接删除该el-col及其内容
// 环形图优化：label只显示大于10%的扇区，legend只显示类型名
const renderTypePie = () => {
  if (!typePie.value) return;
  const chart = echarts.init(typePie.value);
  const typeMap = {};
  infoList.value.forEach(item => {
    const type = item.price_name;
    typeMap[type] = (typeMap[type] || 0) + 1;
  });
  const data = Object.entries(typeMap).map(([name, value]) => ({ name, value }));
  chart.setOption({
    tooltip: { trigger: 'item', formatter: '{b}: {c} ({d}%)' },
    series: [{
      name: '类型分布',
      type: 'pie',
      radius: ['60%', '80%'],
      center: ['50%', '50%'],
      avoidLabelOverlap: false,
      label: { show: false },
      labelLine: { show: false },
      data,
      emphasis: { scale: true }
    }],
    color: ['#4fc3f7', '#81c784', '#ffd54f', '#ff8a65', '#ba68c8', '#e57373', '#64b5f6', '#ffd740', '#a1887f', '#90caf9'],
    textStyle: { fontFamily: 'Microsoft YaHei', fontSize: 14 }
  });
};

// 优化趋势图美观
const renderTrendLine = (type = trendType.value) => {
  if (!trendLine.value) return;
  const chart = echarts.init(trendLine.value);
  let timeSet = new Set();
  let timeMap = {};
  infoList.value.forEach(item => {
    if (item.price_name === type) {
      (item.values || []).forEach(v => {
        if (v.time_point) {
          timeSet.add(v.time_point);
          if (!timeMap[v.time_point]) timeMap[v.time_point] = [];
          if (v.price_amount != null) {
            timeMap[v.time_point].push(Number(v.price_amount));
          }
        }
      });
    }
  });
  // 生成24小时时间段横坐标
  const get24Hours = () => {
    // 取最早的日期
    let baseDate = new Date();
    if (timeSet.size > 0) {
      const sorted = Array.from(timeSet).sort();
      baseDate = new Date(sorted[0]);
    }
    const year = baseDate.getFullYear();
    const month = baseDate.getMonth() + 1;
    const day = baseDate.getDate();
    const pad = n => n.toString().padStart(2, '0');
    const arr = [];
    for (let i = 0; i < 24; i++) {
      arr.push(`${month}-${day} ${pad(i)}:00`);
    }
    return arr;
  };
  const xLabels = get24Hours();
  // 反查原始time字符串
  const timeMapReverse = {};
  Array.from(timeSet).forEach(t => {
    const date = new Date(t);
    const label = `${date.getMonth() + 1}-${date.getDate()} ${date.getHours().toString().padStart(2, '0')}:00`;
    timeMapReverse[label] = t;
  });
  // 组装y轴数据
  const values = xLabels.map(label => {
    const t = timeMapReverse[label];
    if (t && timeMap[t] && timeMap[t].length) {
      return (timeMap[t].reduce((a, b) => a + b, 0) / timeMap[t].length).toFixed(2);
    }
    return 0;
  });
  chart.setOption({
    grid: { left: 60, right: 40, top: 40, bottom: 60 },
    tooltip: { trigger: 'axis' },
    xAxis: {
      type: 'category',
      data: xLabels,
      axisLabel: {
        fontFamily: 'Microsoft YaHei',
        fontSize: 13,
        rotate: 30,
        interval: 0,
        hideOverlap: true
      }
    },
    yAxis: { type: 'value', min: 0, axisLabel: { fontFamily: 'Microsoft YaHei', fontSize: 12 } },
    series: [{
      data: values,
      type: 'line',
      smooth: true,
      symbolSize: 8,
      itemStyle: { color: '#ffa726' },
      lineStyle: { width: 4 },
      label: { show: false }
    }],
    textStyle: { fontFamily: 'Microsoft YaHei', fontSize: 12 }
  });
};

// 柱状图自动刷新，ref绑定在第四张卡片
const renderTypeBar = () => {
  if (!typeBar.value) return;
  const chart = echarts.init(typeBar.value);
  const typeMap = {};
  infoList.value.forEach(item => {
    const type = item.price_name;
    if (!typeMap[type]) typeMap[type] = [];
    (item.values || []).forEach(v => {
      if (v.price_amount != null) typeMap[type].push(Number(v.price_amount));
    });
  });
  const types = Object.keys(typeMap);
  const values = types.map(type => {
    const arr = typeMap[type];
    return arr.length ? (arr.reduce((a, b) => a + b, 0) / arr.length).toFixed(2) : 0;
  });
  const hasData = values.some(v => v > 0);
  chart.setOption({
    grid: { left: 60, right: 40, top: 40, bottom: 60 },
    tooltip: {},
    xAxis: {
      type: 'category',
      data: types,
      axisLabel: { fontFamily: 'Microsoft YaHei', fontSize: 16, fontWeight: 'bold', interval: 0 }
    },
    yAxis: { type: 'value', min: 0, axisLabel: { fontFamily: 'Microsoft YaHei', fontSize: 14 } },
    series: [{
      data: values,
      type: 'bar',
      itemStyle: { color: '#1976d2' },
      barWidth: 48,
      label: {
        show: hasData,
        position: 'top',
        fontFamily: 'Microsoft YaHei',
        fontSize: 18,
        fontWeight: 'bold',
        color: '#1976d2',
        formatter: v => v.value > 0 ? v.value : ''
      }
    }],
    textStyle: { fontFamily: 'Microsoft YaHei', fontSize: 14 },
    graphic: !hasData ? [{
      type: 'text',
      left: 'center',
      top: '40%',
      style: { text: '暂无数据', fontSize: 18, fill: '#888' }
    }] : []
  });
};

// 自动刷新柱状图
watch(infoList, () => {
  nextTick(() => {
    renderTypePie();
    renderTypeBar();
  });
}, { deep: true, immediate: true });

onMounted(() => {
  getList();
});
// 2. 切换类型时，平均电价和趋势图联动
watch(selectedType, (val) => {
  if (val && val !== '全部') {
    trendType.value = val;
    nextTick(() => renderTrendLine(val));
  }
});

// 获取数据列表
const getList = async () => {
  open.value = false;
  loading.value = true;
  try {
    const res = await listInfo(queryParams);
    infoList.value = res.data.data || [];
    total.value = res.data.total || 0;

    // 关键修复：预加载所有时段数据
    await preloadAllTimeData(infoList.value);
  } catch (error) {
    ElMessage.error('获取数据失败');
  } finally {
    loading.value = false;
  }
};


// 新增方法：预加载所有时段数据
const preloadAllTimeData = async (mainData) => {
  // 逐个获取每个电价类型的时段数据
  for (const item of mainData) {
    const priceId = item.price_id;
    try {
      // 标记为加载中
      expandedLoading.value[priceId] = true;

      // 获取时段数据
      const response = await getInfo(priceId);
      const { time_list, value_list } = response.data.data;

      // 合并时间和电价数据
      item.values = time_list.map((time, index) => ({
        time_point: time,
        price_amount: value_list[index] || 0
      }));
    } catch (error) {
      console.error(`加载ID为${priceId}的时段数据失败:`, error);
      item.values = []; // 出错时设为空数组
    } finally {
      expandedLoading.value[priceId] = false;
    }
  }
  // 触发视图更新
  infoList.value = [...infoList.value];

}



// 重置表单
const reset = () => {

  form.period_unit = 'day';
  form.period = 1;
  form.price_type = null;
  form.granularity = 24;
  form.price_name = null;

  formRef.value?.resetFields();
};

// 搜索操作
const handleQuery = () => {
  queryParams.pageNum = 1;
  getList();
};

// 重置搜索
const resetQuery = () => {
  queryParams.period_unit = null;
  queryParams.period = null;
  queryParams.price_type = null;
  queryParams.granularity = null;
  queryParams.price_name = null;

  queryFormRef.value?.resetFields();
  handleQuery();
};

// 多选框选中变化
const handleSelectionChange = (selection) => {
  ids.value = selection.map(item => item.price_id);
  console.log(ids.value);
  single.value = selection.length !== 1;
  multiple.value = !selection.length;
};

// 新增操作
const handleAdd = () => {
  console.log("新增操作")
  reset();
  title.value = "添加电价信息";
  open.value = true;
};

// 修改操作
const handleUpdate = async (row) => {
  reset();
  const priceId = row?.priceId || ids.value[0];

  if (!priceId) {
    return ElMessage.warning('请选择要修改的数据');
  }

  try {
    const response = await getInfo(priceId);
    Object.assign(form, response.data);
    open.value = true;
    title.value = "修改电价信息";
  } catch (error) {
    ElMessage.error('获取数据失败');
  }
};

// 提交表单
const submitForm = () => {
  const requiredCount = 24;
  if (!form.values || form.values.length < requiredCount) {
    const left = requiredCount - (form.values ? form.values.length : 0);
    ElMessage.warning(`还需输入${left}条数据`);
    return;
  }
  formRef.value.validate(valid => {
    if (!valid) {
      ElMessage.error('请填写必填字段');
      return;
    }
    // 构建符合后端要求的数据对象
    const payload = {
      period_unit: form.period_unit,
      period: Number(form.period), // 转换为数值
      price_type: Number(form.price_type), // 转换为数值
      granularity: form.granularity,
      price_name: form.price_name, // 修正字段名
      values: form.values.map(item => ({
        ...item,
        time_point: formatToISODate(item.time_point), // 转换时间格式
        price_amount: Number(item.price_amount) // 确保为数值
      }))
    };
    console.log('提交的数据:', JSON.stringify(form, null, 2));
    const action = form.priceId ? updateInfo(payload) : addInfo(payload);

    action.then(() => {
      ElMessage.success(form.priceId ? '修改成功' : '新增成功');
      open.value = false;
      getList();
    }).catch(error => {
      ElMessage.error('操作失败: ' + (error.message || '未知错误'));
    });
  });
};

// 删除操作
const handleDelete = async (row) => {
  const priceId = row.price_id;

  delInfo(priceId).then(() => {
    ElMessage.success('删除成功');
    getList();
  }).catch(error => { // 处理异常
    ElMessage.error('删除失败: ' + (error.message || '未知错误'));
  });
};

// 批量删除操作
const handleBatchDelete = async () => {
  const priceIds = ids.value.join(',');

  if (!priceIds) {
    return ElMessage.warning('请选择要删除的数据');
  }
  try {
    await ElMessageBox.confirm(`是否确认删除编号为"${priceIds}"的数据？`, '提示', {
      confirmButtonText: '确定',
      cancelButtonText: '取消',
      type: 'warning'
    });

    // await delInfo(priceIds);
    // ElMessage.success('删除成功');
    // getList();
  } catch (error) {
    // 取消删除
  }
};
//根据id批量删除
const deleteByIds = () => {
  deleteInfoByIds({
    price_ids: ids.value
  }).then(() => {
    ElMessage.success('删除成功');
    getList();
  }).catch(error => {
    ElMessage.error('删除失败: ' + (error.message || '未知错误'));
  });
}
const exportByIds = () => {
  exportInfoByIds({
    price_ids: ids.value
  }).then((res) => {
    downloadFile(res.data, '电价信息.xlsx');
    ElMessage.success('导出成功');
  }).catch(error => {
    ElMessage.error('导出失败: ' + (error.message || '未知错误'));
  });
};

const predictByIds = () => {
  // 1. 验证是否只勾选了一条数据
  if (ids.value.length !== 1) {
    ElMessage.warning('请勾选一条数据进行预测');
    return;
  }

  // 2. 获取选中数据的 price_id
  const selectedPriceId = ids.value[0];
  // console.log(selectedPriceId)

  // 3. 从数据源中查找完整数据对象
  const selectedRecord = infoList.value.find(item => item.price_id === selectedPriceId);

  // 4. 校验是否找到数据
  if (!selectedRecord) {
    ElMessage.error('找不到选中的数据，请刷新后重试');
    return;
  }

  // 5. 映射 price_type 到接口需要的类型（0→solar，1→wind，2→grid）
  const typeMap = { 0: 'solar', 1: 'wind', 2: 'grid' };
  const type = typeMap[selectedRecord.price_type];

  if (type === undefined) {
    ElMessage.error('未知的电价类型，请检查数据');
    return;
  }

  // 6. 调用预测接口
  predictElectricPrice(type, selectedPriceId)
    .then((res) => {
      ElMessage.success('预测成功');
      // 可根据接口返回结果处理，例如展示预测数据
      const predictedData = res.data.data || {};
      getList();
      console.log('预测结果:', res.data);
    })
    .catch((error) => {
      ElMessage.error('预测失败: ' + (error.message || '未知错误'));
    });

};


// 导出操作
const handleExport = (props) => {
  const data = props.values.map(row => ({
    时间点: row.time_point,
    价格: row.price_amount
  }));
  console.log(props)
  // 2. 转为sheet
  const worksheet = XLSX.utils.json_to_sheet(data);
  const workbook = XLSX.utils.book_new();
  XLSX.utils.book_append_sheet(workbook, worksheet, props.price_name);

  // 3. 导出
  XLSX.writeFile(workbook, props.price_name + ".xlsx");
};

// 取消操作
const cancel = () => {
  open.value = false;
  reset();
};

const avgPrice = computed(() => {
  // 统计所有infoList的values中的price_amount平均值
  let total = 0, count = 0;
  infoList.value.forEach(item => {
    (item.values || []).forEach(v => {
      if (v.price_amount != null) {
        total += Number(v.price_amount);
        count++;
      }
    });
  });
  return count ? (total / count).toFixed(2) : 0;
});
</script>

<style scoped>
.elec-bg {
  min-height: 100vh;
  background-color: #f9fbfd;
  color: #222;
  font-family: Arial, sans-serif;
  padding: 0 0;
}

.elec-card {
  background: #FFFFFF;
  border-radius: 10px;
  border: 1px solid #d1d7dc;
  margin: 20px auto;
  box-shadow: 0 2px 8px rgba(90, 150, 255, 0.08);
  max-width: 1400px;
}

.card-title {
  font-size: 20px;
  font-weight: bold;
  color: #1976d2;
}

.stat-row {
  margin-bottom: 20px;
}

.stat-card {
  text-align: center;
  background: linear-gradient(to bottom right, #e3f2fd, #bbdefb);
  border: 1px solid #90caf9;
  border-radius: 10px;
  min-height: 120px;
  height: 140px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  box-sizing: border-box;
  padding: 0 10px;
}

.stat-value {
  font-size: 28px;
  font-weight: bold;
  margin-top: 18px;
}

.stat-label {
  font-size: 14px;
  margin-top: 5px;
}

/* 覆盖图标容器的行高 */
:deep(.el-input__icon) {
  line-height: 1 !important;
}

/* 确保图标正确显示的关键样式 */
.icon-btn {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  /* 图标与文字间距 */
}

/* 强制设置图标尺寸（解决0*0问题） */
:deep(.el-icon) {
  width: 14px !important;
  height: 14px !important;
  display: inline-block !important;
}

/* 修复可能的样式冲突 */
:deep(svg) {
  width: 14px !important;
  height: 14px !important;
  vertical-align: middle;
  text-align: center;
}

.add-button-container {
  text-align: right;
  margin-bottom: 10px;
}

.table-container_dialog {
  width: 100%;
}

.expand-container {
  padding: 15px;
}

/* 左右分栏布局 */
.split-layout {
  display: flex;
  gap: 20px;
  /* 两栏间距 */
  width: 100%;
}

/* 左侧图表容器（40%宽度） */
.chart-container {
  width: 50%;
  height: 300px;
  /* 固定高度，确保图表显示 */
  min-width: 300px;
  /* 最小宽度，避免过窄 */
  border: 1px solid #ebeef5;
  border-radius: 4px;
}

/* 右侧表格容器（60%宽度） */
.table-container {
  width: 50%;
  min-width: 400px;
  /* 最小宽度，避免表格变形 */
}

/* 子表格列宽优化 */
:deep(.el-table .el-table__cell) {
  padding: 8px 0;
}

.chart-row {
  margin-bottom: 20px;
}

.chart-card {
  background: linear-gradient(to bottom right, #e3f2fd, #bbdefb);
  border: 1px solid #90caf9;
  border-radius: 10px;
  min-height: 320px;
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  justify-content: flex-start;
  box-sizing: border-box;
  padding: 20px 20px 10px 20px;
}

.chart-title {
  font-size: 16px;
  font-weight: bold;
  color: #1976d2;
  margin-bottom: 10px;
}

.echart-box {
  width: 100%;
  height: 300px;
}

.action-btn-row {
  margin-bottom: 18px;
  display: flex;
  align-items: center;
  gap: 12px;
}

.action-btn {
  border-radius: 20px !important;
  font-size: 15px !important;
  font-weight: 500;
  min-width: 90px;
  height: 38px;
  box-shadow: 0 2px 8px rgba(90, 150, 255, 0.08);
  transition: all 0.2s;
  margin-right: 8px;
  letter-spacing: 1px;
}

.action-btn.primary {
  background: #64b5f6 !important;
  color: #1976d2 !important;
  border: none;
}

.action-btn.primary:hover {
  color: #fff !important;
  background: #42a5f5 !important;
}

.action-btn.danger {
  background: #ef9a9a !important;
  color: #b71c1c !important;
  border: none;
}

.action-btn.danger:hover {
  color: #fff !important;
  background: #e57373 !important;
}

.action-btn.warning {
  background: #ffe082 !important;
  color: #bfa100 !important;
  border: none;
}

.action-btn.warning:hover {
  color: #fff !important;
  background: #ffd54f !important;
}

.action-btn.success {
  background: #a5d6a7 !important;
  color: #388e3c !important;
  border: none;
}

.action-btn.success:hover {
  color: #fff !important;
  background: #66bb6a !important;
}
:deep(.action-btn.import) {
  background: #e1bee7 !important; /* 淡紫色 */
  color: #6a1b9a !important;
  border: none;
}
:deep(.action-btn.import:hover) {
  color: #fff !important;
  background: #ab47bc !important;
}
.action-btn:disabled,
.action-btn[disabled] {
  opacity: 0.5;
  cursor: not-allowed;
  background: #e0e0e0 !important;
  color: #aaa !important;
  border: none !important;
}

.elect-form {
  background: #ffffff;
  border-radius: 12px;
  padding: 10px;
  box-shadow: 0 4px 12px rgba(0, 0, 0, 0.05);
}
:deep(.elect-form .el-form-item) {
  margin-bottom: 24px;
}
:deep(.elect-form .el-form-item__label) {
  color: #374151;
  font-weight: 500;
  font-size: 14px;
  line-height: 1.5;
}
:deep(.elect-form .el-form-item__content) {
  line-height: 1;
}
.form-input, .form-select {
  border-radius: 8px;
  transition: all 0.3s ease;
  width: 100%;
}
:deep(.form-input .el-input__wrapper),
:deep(.form-select .el-select__wrapper) {
  border-radius: 8px;
  box-shadow: 0 2px 4px rgba(0, 0, 0, 0.05);
  border: 1px solid #e5e7eb;
  transition: all 0.3s ease;
  background: #ffffff;
}
:deep(.form-input .el-input__wrapper:hover),
:deep(.form-select .el-select__wrapper:hover) {
  border-color: #90caf9;
  box-shadow: 0 4px 8px rgba(25, 118, 210, 0.1);
}
:deep(.form-input .el-input__wrapper.is-focus),
:deep(.form-select .el-select__wrapper.is-focus) {
  border-color: #1976d2;
  box-shadow: 0 0 0 3px rgba(25, 118, 210, 0.1);
}

:deep(.form-input .el-input__inner),
:deep(.form-select .el-select__selected-item) {
  color: #374151;
  font-size: 14px;
  padding: 5px 10px;
}
:deep(.form-input .el-select__selected-item.is-transparent) {
  color: #9ca3af;
  font-size: 14px;
}
:deep(.form-input .el-input__inner::placeholder),
:deep(.form-select .el-select__selected-item.is-transparent) {
  color: #9ca3af;
  font-size: 14px;
  opacity: 1;
}
:deep(.form-select .el-select__wrapper.is-disabled){
  background: #f5f7fa !important;
  border: 1px solid #e5e7eb !important;
}
:deep(.form-select .el-select__selected-item.is-placeholder) {
  color: #9ca3af !important;
  font-size: 14px !important;
  opacity: 1 !important;
}
.add-btn {
  background: linear-gradient(135deg, #1976d2 0%, #42a5f5 100%);
  border: none;
  box-shadow: 0 2px 8px rgba(25, 118, 210, 0.2);
  transition: all 0.3s ease;
}

.add-btn:hover {
  transform: translateY(-2px);
  box-shadow: 0 4px 12px rgba(25, 118, 210, 0.3);
}
.cancel-btn {
  border-radius: 8px;
  padding: 10px 24px;
  margin-top: 10px;
  font-weight: 500;
  border: 1px solid #d1d5db;
  color: #6b7280;
  background: #ffffff;
  transition: all 0.3s ease;
}
.cancel-btn:hover {
  border-color: #9ca3af;
  color: #374151;
  background: #f9fafb;
  transform: translateY(-1px);
  box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1);
}
.confirm-btn {
  border-radius: 8px;
  padding: 10px 24px;
  font-weight: 500;
  margin-top: 10px;
  background: linear-gradient(135deg, #1976d2 0%, #42a5f5 100%);
  border: none;
  color: #ffffff;
  transition: all 0.3s ease;
}
.confirm-btn:hover {
  background: linear-gradient(135deg, #1565c0 0%, #1976d2 100%);
  transform: translateY(-1px);
  box-shadow: 0 6px 16px rgba(25, 118, 210, 0.3);
}
.confirm-btn:active {
  transform: translateY(0);
  box-shadow: 0 2px 8px rgba(25, 118, 210, 0.2);
}
.dialog-footer {
  display: flex;
  justify-content: flex-end;
  gap: 12px;
}
</style>